#define  _CRT_SECURE_NO_WARNINGS 1
#include "Slist.h"
SLT* BuySListNode(SLTDataType x)
{
	SLT* newnode = (SLT*)malloc(sizeof(SLT));
	if (!newnode)
	{
		perror("BuySListNode");
		exit(-1);
	}
	newnode->data = x;
	newnode->next = NULL;

	return newnode;
}

void SLPrint(SLT* phead)
{
	SLT* curr = phead;
	while (curr)
	{
		printf("%d ", curr->data);
		curr = curr->next;
	}
	printf("NULL\n");
}

void SLPushBack(SLT** pphead, SLTDataType x)
{
	assert(pphead);

	SLT* newnode = BuySListNode(x);
	if (*pphead == NULL)
	{
		*pphead = newnode;
	}
	else
	{
		SLT* curr = *pphead;
		while (curr->next)
		{
			curr = curr->next;
		}
		curr->next = newnode;
	}
}

void SLPushFront(SLT** pphead, SLTDataType x)
{
	assert(pphead);

	SLT* newnode = BuySListNode(x);
	newnode->next = *pphead;
	*pphead = newnode;
}

void SLPopBack(SLT** pphead)
{
	assert(pphead);
	assert(*pphead);

	if ((*pphead)->next == NULL)
	{
		free(*pphead);
		*pphead = NULL;
	}
	else
	{
		SLT* tailPrev = *pphead;
		while (tailPrev->next->next)
		{
			tailPrev = tailPrev->next;
		}
		free(tailPrev->next);
		tailPrev->next = NULL;
	}
}

void SLPopFront(SLT** pphead)
{
	assert(pphead);
	assert(*pphead);

	SLT* del = *pphead;
	*pphead = (*pphead)->next;
	free(del);
}

SLT* SLFind(SLT* phead, SLTDataType x)
{
	SLT* curr = phead;
	while (curr)
	{
		if (curr->data == x)
			return curr;
		curr = curr->next;
	}
	return NULL;
}

void SLInsert(SLT** pphead, SLT* pos, SLTDataType x)
{
	assert(pphead);
	assert(pos);

	if (*pphead == pos)
	{
		SLPushFront(pphead, x);
	}
	else
	{
		SLT* posPrev = *pphead;
		while (posPrev->next != pos)
		{
			posPrev = posPrev->next;
		}
		SLT* newnode = BuySListNode(x);
		posPrev->next = newnode;
		newnode->next = pos;
	}
}

void SLInsertAfter(SLT* pos, SLTDataType x)
{
	assert(pos);

	SLT* newnode = BuySListNode(x);
	newnode->next = pos->next;
	pos->next = newnode;
}

void SLErase(SLT** pphead, SLT* pos)
{
	assert(pphead);
	assert(*pphead);
	assert(pos);

	if (*pphead == pos)
	{
		SLPopFront(pphead);
	}
	else
	{
		SLT* posPrev = *pphead;
		while (posPrev->next != pos)
		{
			posPrev = posPrev->next;
		}
		posPrev->next = pos->next;
		free(pos);
	}
}

void SLEraseAfter(SLT* pos)
{
	assert(pos);
	assert(pos->next);

	SLT* posNext = pos->next;
	pos->next = posNext->next;
	free(posNext);
}

void SLDestroy(SLT** pphead)
{
	assert(pphead);

	SLT* curr = *pphead;
	while (curr)
	{
		SLT* del = curr;
		curr = curr->next;
		free(del);
	}
	*pphead = NULL;
}